import pymongo

collection = 0
db = pymongo.MongoClient().chapter_7
example_data_2 = db.example_data_2

# 使用点号定位到嵌套字段user中的子字段userid为102的数据
db.getCollection('example_data_2').find({
    'user.user_id': 102
})
# 查询”folloed“ 大于10的数据
db.getCollection('example_data_2').find({
    'user.followed': {'$gt': 10}
})

db.getCollection('example_data_2').find({
    'user.followed': {'$gt': 10}
},
    {'_id': 0, 'user.name': 1, 'user.user_id': 1})

# 查询age大于等于20且sex 为女的全部记录
db.getCollection('example_data_1').aggregate([{'$match': {
    'age': {'$gte': 20},
    'sex': '女'
}}])
# 等价于
db.getCollection('example_data_1').find({
    'age': {'$gte': 20},
    'sex': '女'
})
# 查询所有age大于28或者sex 为男的记录
db.getCollection('example_data_1').aggregate([
    {'$match': {'$or': [{'age': {'$gt': 28}}, {'sex': '男'}]}}
])

collection.aggregate([{'$project': {字段过滤语句}}])
# 不返回_id 字段，只返回age和sex字段
db.getCollection('example_data_1').aggregate([
    {'$project': {'_id': 0, 'sex': 1, 'age': 1}}

])
# 结合 $match实现，先赛选记录后过滤字段， 选择所有age大于28的记录，只返回age 和sex
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'age': 1, 'sex': 1}}
])
# 添加固定文本：在`$project` 的 value字典中添加一个不存在的字段
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'age': 1, 'sex': 1, 'hello': 'world'}}
])
# 复制现有字段：world---> $age
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'age': 1, 'sex': 1, 'hello': '$age'}}
])
# 修改现有字段的数据
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'sex': 1, 'age': 'this is age '}}
])
# 直接使用find(). 想返回 user_id 和 name
db.getCollection('example_data_2').find({}, {'user.name': 1, 'user.user_id': 1})
# 结果还是嵌套字段，不大方便，使用$project 则可以将嵌套字段转化为普通字段
db.getCollection('example_data_2').aggregate([
    {'$project': {'name': '$user.name', 'user_id': '$user.user_id'}}
])

# 添加一个字段，一个字段的值为数字 ‘1’
# 添加一个字段，一个字段为普通字符串，但是开头以$ 开头
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'id': 1, 'hello': '$normalstring', 'abcd': 1}}
])
# 以上都不能添加成功，需要使用$literal
db.getCollection('example_data_1').aggregate([
    {'$match': {'age': {'$gt': 28}}},
    {'$project': {'_id': 0, 'id': 1, 'hello': {'$literal': 'normalstring'}, 'abcd': {'$literal': 1}}}
])
# 使用distinct 函数对 name 字段去重
db.getCollection('example_data_4').distinct('姓名')  # 返回一行
# 使用分组操作去重
collection.aggregate([
    {'$group': {'_id': '$被去重的字段名'}}
])
db.getCollection('example_data_4').aggregate([
    {'$group': {'_id': '$姓名'}}
])

# 聚合计算语法
collection.aggregate([
    {'$group': {'_id': '$被去重的字段名',
                'max_score': {'$max': '$字段名'},
                'min_score': {'$min': '$字段名'},
                'avg_score': {'$avg': '$字段名'},
                'sum_score': {'$sum': '$字段名'}
                }}
])
# 对数据集example_data_4进行分组聚合，计算每个人得分的最大值最小值得分之和和平均数
db.getCollection('example_data_4').aggregate([
    {'$group': {'_id': '$姓名',
                'max': {'$max': '$分数'},
                'min': {'$min': '$分数'},
                'sum': {'$sum': '$分数'},
                'avg': {'$avg': '$分数'},
                'count': {'$sum': 1}
                }}
])

# 以name 为基准去重，然后取各个字段的最新数据
db.getCollection('example_data_4').aggregate([
    {'$group': {'_id': '$name',
                'date': {'$last': '$date'},
                'score': {'$last': '$score'}}}
])
# 以name 为基准去重，然后取各个字段的最旧数据
db.getCollection('example_data_4').aggregate([
    {'$group': {'_id': '$name',
                'date': {'$first': '$date'},
                'score': {'$first': '$score'}}}
])

# 语法
collection.aggregate([
    {'$unwind': '$字段名'}
])
# 对size拆开
db.getCollection('example_data_3').aggregate([
    {'$unwind': '$size'}
])

# 联集合查询的语法
主集合.aggregate([
    {'$lookup': {
        'from': '被查集合名',
        'localField': '主集合的字段',
        'foreignField': '被查集合的字段',
        'as': '保存查询结果的字段名'
    }}
])

# 需要在微博集合查询用户信息，那么主集合就是微博集合，被查集合就是用户集合
db.getCollection('example_post').aggregate([
    {'$lookup': {
        'from': 'example_user',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }}
])
# 联集合查询并美化
db.getCollection('example_post').aggregate([
    {'$lookup': {
        'from': 'example_user',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }},
    {'$unwind': '$user_info'}
])
# 联集合查询并拆分结果数据在返回特定内容
db.getCollection('example_post').aggregate([
    {'$lookup': {
        'from': 'example_user',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }},
    {'$unwind': '$user_info'},
    {'$project': {'content': 1,
                  'post_time': 1,
                  'name': '$user_info.name',
                  'work': '$user_info.work'}}
])

# 查询每个用户的发微博情况 ，已知每一个用户，想知道哪些用户发了那些微博。
# 主集合变为用户集合，被查询集合变为微博集合
# 需要在微博集合查询用户信息，那么主集合就是微博集合，被查集合就是用户集合
db.getCollection('example_user').aggregate([
    {'$lookup': {
        'from': 'example_post',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': '$weibo_info'
    }}
])
# 用户为基准联集合查询，再拆分结果，最后输出指定内容

db.getCollection('example_user').aggregate([
    {'$lookup': {
        'from': 'example_post',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }},
    {'$unwind': '$user_info'},
    {'$project': {'name': 1,
                  'work': 1,
                  'content': '$weibo_info.content',
                  'post_time': '$weibo_info.post_time'}}
])

# 集合操作优先数据 名字为张小二的发言
db.getCollection('example_user').aggregate([
    {'$match': {'name': '张小二'}},
    {'$lookup': {
        'from': 'example_post',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }},
    {'$unwind': '$user_info'},
    {'$project': {'name': 1,
                  'work': 1,
                  'content': '$weibo_info.content',
                  'post_time': '$weibo_info.post_time'}}
])
# 集合操作先联集合查询后再赛选数据写法
db.getCollection('example_user').aggregate([

    {'$lookup': {
        'from': 'example_post',
        'localField': 'user_id',
        'foreignField': 'id',
        'as': 'user_info'
    }},
    {'$match': {'name': '张小二'}},
    {'$unwind': '$user_info'},
    {'$project': {'name': 1,
                  'work': 1,
                  'content': '$weibo_info.content',
                  'post_time': '$weibo_info.post_time'}}
])
